#include "net.h"
 
int create_listen_ports(int port, int proto, unsigned char* addr, int reuse)
{
	int fd = -1;
	fd = create_socket(port, proto, addr, reuse);
	if (fd < 0 || set_non_block(fd) < 0) {
		printf("port:%d,proto:%d\n", port, proto);
	}
	return fd;
}


int create_socket(int port, int proto, unsigned char* addr, int reuse)
{
	int fd = -1, pt = -1;
	struct sockaddr_in srv;

	pt = proto;
	fd = socket(AF_INET, pt, 0);
	if (fd <= 0)
		return -1;
	srv.sin_family = AF_INET;
	if (addr == NULL)
		srv.sin_addr.s_addr = htonl(INADDR_ANY);
	else
		/* inet_aton(addr, &srv.sin_addr); */
		inet_pton(AF_INET, (const char *)addr, &srv.sin_addr);
	srv.sin_port = htons(port);
	if (reuse > 1)
		set_reuse(fd);
	if (bind(fd, &srv, sizeof(srv)) < 0) {
		perror("bind:");
		return -1;
	}
	if (proto == SOCK_STREAM)
		listen(fd, 512);
	return fd;
}

int set_sock_buff(int fd, int bytes)
{
	int ret;     
	if (fd <= 0)
		return -1;

	return setsockopt(fd, SOL_SOCKET, SO_RCVBUF, (const unsigned char*)&bytes, sizeof(int));
}


int set_non_block(int fd)
{
	int opt = fcntl(fd, F_GETFL, 0);
	if (opt < 0)
		return -1;
	//opt |= O_NONBLOCK;
	return (fcntl(fd, F_SETFL, opt));
}

int set_reuse(int fd)
{
	int nOptval = 1;
	return setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (const void *)&nOptval, sizeof(int));
}



int make_addr_from_bin(struct sockaddr_in *addr, unsigned char * data)
{
	unsigned char ipv4[16] = { 0 };
	int idx = 0;
	int i;
	unsigned char val = 0;
	if (data[0] == 0 && data[1] == 0 && data[2] == 0 && data[3] == 0)
		return -1;
	for (i = 0; i < 4; i++) {
		val = (unsigned char)data[i];
		if (val > 99) {
			ipv4[idx] = val / 100 + '0';
			idx++;
		}
		if (val > 9) {
			ipv4[idx] = (val % 100) / 10 + '0';
			idx++;
		}
		ipv4[idx] = val % 10 + '0';
		idx++;
		ipv4[idx] = '.';
		idx++;
	}
	ipv4[idx - 1] = 0;
	i = inet_pton(AF_INET, (const unsigned char *)ipv4, &addr->sin_addr);
	return 0;
}

